module WegoLint; end

require 'stringio'

class WegoLint::WegoLinter
  def initialize(filename)
    @filename = filename
    @filetype = File.extname(@filename)
    @ruleset = @filetype == '.js' ? :javascript : :ruby
    @output = ''
  end

  def lint!
    @output = run_language_parser
    parse_file
  end

  def rules
    WegoLint::RuleRegistry.instance.rules
  end

  def output
    @output
  end

  def load_rules
    WegoLint::RuleRegistry.instance.load_rules
  end

  ##############################################################################
  private

  def parse_file
    File.open(@filename, 'r') do |file|
      text = file.read
      apply_rules(text, :general)
      apply_rules(text, @ruleset)
    end
  end

  def run_language_parser
    if @filetype == ".js"
      command = 'jsl -nologo -nofilelisting -nosummary -nocontext -process'
      `#{command} #{@filename} 2>&1`
    else
      `ruby -w -T1 -c #{@filename} 2>&1`
    end
  end

  def apply_rules(text, ruleset = :general)
    return unless rules[ruleset]
    rules[ruleset].each do |key, rule|
      rule.run(text)
      @output += format_errors(rule.errors) + "\n" unless rule.errors.empty?
    end
  end

  def format_errors(errors)
    errors.collect { |error| format_error(error) }.join("\n")
  end

  def format_error(error)
    if @ruleset == :ruby
      "#{@filename}:#{error[:line_number]}: syntax error, #{error[:message]}"
    elsif @ruleset == :javascript
      "#{@filename}:#{error[:line_number]}: error: #{error[:message]}"
    end
  end
end
